Unit console;

Interface
uses ports;

const
        Black = 0;
        Blue = 1;
        Green = 2;
        Cyan = 3;
        Red = 4;
        Magenta = 5;
        Brown = 6;
        LightGray = 7;
        DarkGray = 8;
        LightBlue = 9;
        LightGreen = 10;
        LightCyan = 11;
        LightRed = 12;
        LightMagenta = 13;
        Yellow = 14;
        White = 15;
 
        F1=59;
        F2=60;
        F3=61;
        F4=62;
        F5=63;
        F6=64;
        F7=65;
        F8=66;
        F9=67;
        F10=68;
        F11=87;
        F12=88;
        Enter=28;
        Crtl=29;
        Alt=56;
        BkSpc=14;
        Space=57;
        Shift=42;
        CapsLock=58;
        up=72 ;
        left=75;
        right=77;
        down=80 ;
 
        tblchar : array [1..57] of PChar=
           ('0','1','2','3','4','5','6','7','8','9','0','?','=','0',' ',
           'Q','W','E','R','T','Y','U','I','O','P','[',']','0','0',
           'A','S','D','F','G','H','J','K','L',' ','{','}','0','0',
           'Z','X','C','V','B','N','M',',','.','/','0','*','0',' ');

Var
  xpos: Integer = 0;
  ypos: Integer = 0;

Procedure kclearscreen();
Procedure kwritechr(c: Char);
Procedure kwritestr(s: PChar);
Procedure kwriteint(i: Integer);
Procedure kwritedword(i: DWORD);
procedure kwritestrln(s: PChar);
procedure kread(s: PChar);

Implementation

Var
  vidmem: PChar = PChar($b8000);

procedure kread(s: PChar);
var
  b:byte;
  c:byte;

begin
  repeat
    b:=inportb($60);
    if (b<>c) and (b<>0) and (b<57) and (b>0) then 
    begin
      kwritestr(tblchar[b]);
    end;
	if b<>c then c:=b;
    b:=0;
    
  until b=72;
end;


Procedure kclearscreen();[Public , alias: 'kclearscreen'];

Var
  i: Integer;
Begin
  For i := 0 To 3999 Do
    vidmem[i] := #0;
  xpos:=0;
  ypos:=0;
End;

Procedure kwritechr(c: Char);[Public , alias: 'kwritechr'];

Var
  offset: Integer;
Begin
  If (ypos > 24) Then
    ypos := 0;

  If (xpos > 79) Then
    xpos := 0;

  offset := (xpos shl 1) + (ypos * 160);
  vidmem[offset] := c;
  offset += 1;
  vidmem[offset] := #7;
  offset += 1;

  xpos := (offset Mod 160);
  ypos := (offset - xpos) Div 160;
  xpos := xpos shr 1;
End;

Procedure kwritestr(s: PChar);
[
Public , alias: 'kwritestr'];

Var
  offset, i: Integer;
Begin
  If (ypos > 24) Then
    ypos := 0;

  If (xpos > 79) Then
    xpos := 0;

  offset := (xpos shl 1) + (ypos * 160);
  i := 0;

  While (s[i] <> Char($0)) Do
    Begin
      vidmem[offset] := s[i];
      offset += 1;
      vidmem[offset] := #7;
      offset += 1;
      i += 1;
    End;
  
  xpos := (offset Mod 160);
  ypos := (offset - xpos) Div 160;
  xpos := xpos shr 1;
End;

Procedure kwriteint(i: Integer);
[
Public , alias: 'kwriteint'];

Var
  buffer: array [0..11] Of Char;
  str: PChar;
  digit: DWORD;
  minus: Boolean;
Begin
  str := @buffer[11];
  str^ := #0;

  If (i < 0) Then
    Begin
      digit := -i;
      minus := True;
    End
  Else
    Begin
      digit := i;
      minus := False;
    End;

  Repeat
    Dec(str);
    str^ := Char((digit Mod 10) + Byte('0'));
    digit := digit Div 10;
  Until (digit = 0);

  If (minus) Then
    Begin
      Dec(str);
      str^ := '-';
    End;

  kwritestr(str);
End;

Procedure kwritedword(i: DWORD);
[
Public , alias: 'kwritedword'];

Var
  buffer: array [0..11] Of Char;
  str: PChar;
  digit: DWORD;
Begin
  For digit := 0 To 10 Do
    buffer[digit] := '0';

  str := @buffer[11];
  str^ := #0;

  digit := i;
  Repeat
    Dec(str);
    str^ := Char((digit Mod 10) + Byte('0'));
    digit := digit Div 10;
  Until (digit = 0);

  kwritestr(@Buffer[0]);
End;

Procedure kwritestrln(s: PChar);
[
Public , alias: 'kwritestrln'];

Var
  offset, i: Integer;
Begin
  If (ypos > 24) Then
    ypos := 0;

  If (xpos > 79) Then
    xpos := 0;

  offset := (xpos shl 1) + (ypos * 160);
  i := 0;

  While (s[i] <> Char($0)) Do
    Begin
      vidmem[offset] := s[i];
      offset += 1;
      vidmem[offset] := #7;
      offset += 1;
      i += 1;
    End;
  
  xpos := (offset Mod 160);
  ypos := (offset - xpos) Div 160;
  xpos := xpos shr 1;
  ypos := ypos+1;
  xpos := 0;  
End;

End.
